
#include <BLabel>
#include <BImage>
#include <BIcon>
#include <BVBoxLayout>
#include <BGridLayout>
#include <BHBoxLayout>
#include <BFileDialog>
#include <BColorDialog>

#include "ButtonPanel.h"

ButtonPanel::ButtonPanel(BWidget* parent) : BGroupBox(parent)
{
	_button = 0;

	BLabel* checkableLabel = new BLabel("checkable");
	_checkableCheckBox = new BCheckBox();

	BLabel* formLabel = new BLabel("form");
	_formComboBox = new BComboBox();
	_formComboBox->addItem("None", Form_None);
	_formComboBox->addItem("IconAlone", Form_IconAlone);
	_formComboBox->addItem("TextAlone", Form_TextAlone);
	_formComboBox->addItem("TextOnly", Form_TextOnly);
	_formComboBox->addItem("IconOnly", Form_IconOnly);
	_formComboBox->addItem("IconText", Form_IconText);
	_formComboBox->addItem("TextIcon", Form_TextIcon);
	_formComboBox->addItem("TextUnderIcon", Form_TextUnderIcon);
	_formComboBox->addItem("IconUnderText", Form_IconUnderText);

	BLabel* alignLabel = new BLabel("align");
	_alignButton = new BButton();
	_alignButton->setCheckable(true);
	_alignButton->setAlign(Align_LeftCenter);

	_alignWidget = new AlignWidget(this);
	_alignWidget->setVisible(false);
	_alignWidget->setSize(250, 250);

	BLabel* spacingLabel = new BLabel("spacing");
	_spacingSpinBox = new BSpinBox(0, 20);

	BLabel* colorLabel = new BLabel("color");
	_colorButton = new BButton(Graph_Square_Fill);

	BLabel* graphLabel = new BLabel("graph");
	_graphComboBox = new BComboBox();
	_graphComboBox->addItem("None", Graph_None);
	_graphComboBox->addItem("Space", Graph_Space);
	_graphComboBox->addItem("Circle", Graph_Circle);
	_graphComboBox->addItem("Circle_Fill", Graph_Circle_Fill);
	_graphComboBox->addItem("Square", Graph_Square);
	_graphComboBox->addItem("Square_Fill", Graph_Square_Fill);
	_graphComboBox->addItem("Arrow_Up", Graph_Arrow_Up);
	_graphComboBox->addItem("Arrow_Up_Fill", Graph_Arrow_Up_Fill);
	_graphComboBox->addItem("Arrow_Down", Graph_Arrow_Down);
	_graphComboBox->addItem("Arrow_Down_Fill", Graph_Arrow_Down_Fill);
	_graphComboBox->addItem("Arrow_Left", Graph_Arrow_Left);
	_graphComboBox->addItem("Arrow_Left_Fill", Graph_Arrow_Left_Fill);
	_graphComboBox->addItem("Arrow_Right", Graph_Arrow_Right);
	_graphComboBox->addItem("Arrow_Right_Fill", Graph_Arrow_Right_Fill);
	_graphComboBox->addItem("Plus", Graph_Plus);
	_graphComboBox->addItem("Minus", Graph_Minus);
	_graphComboBox->addItem("Check_Sign", Graph_Check);
	_graphComboBox->addItem("Cross_Sign", Graph_Cross);
	_graphComboBox->addItem("Minimize", Graph_Minimize);
	_graphComboBox->addItem("Maximize", Graph_Maximize);
	_graphComboBox->addItem("Normalize", Graph_Normalize);

	BLabel* imageLabel = new BLabel("image");
	_imageButton = new BButton();
	_imageButton->setAlign(Align_VCenter);

	BLabel* iconLabel = new BLabel("icon");
	_iconButton = new BButton();
	_iconButton->setAlign(Align_VCenter);

	BLabel* textLabel = new BLabel("text");
	_textEdit = new BLineEdit();

	BLabel* iconSizeLabel = new BLabel("icon-size");
	BHBoxLayout* iconSizeLayout = new BHBoxLayout();
	{
		_iconWidthSpinBox = new BSpinBox(0, 100);
		_iconHeightSpinBox = new BSpinBox(0, 100);

		iconSizeLayout->addWidget(_iconWidthSpinBox);
		iconSizeLayout->addWidget(_iconHeightSpinBox);
	}

	BGridLayout* gridLayout = new BGridLayout(this);
	gridLayout->setWidget(0, 0, checkableLabel);
	gridLayout->setWidget(0, 1, _checkableCheckBox);
	gridLayout->setWidget(1, 0, formLabel);
	gridLayout->setWidget(1, 1, _formComboBox);
	gridLayout->setWidget(2, 0, alignLabel);
	gridLayout->setWidget(2, 1, _alignButton);
	gridLayout->setWidget(3, 0, spacingLabel);
	gridLayout->setWidget(3, 1, _spacingSpinBox);
	gridLayout->setWidget(4, 0, colorLabel);
	gridLayout->setWidget(4, 1, _colorButton);
	gridLayout->setWidget(5, 0, graphLabel);
	gridLayout->setWidget(5, 1, _graphComboBox);
	gridLayout->setWidget(6, 0, imageLabel);
	gridLayout->setWidget(6, 1, _imageButton);
	gridLayout->setWidget(7, 0, iconLabel);
	gridLayout->setWidget(7, 1, _iconButton);
	gridLayout->setWidget(8, 0, iconSizeLabel);
	gridLayout->setLayout(8, 1, iconSizeLayout);
	gridLayout->setWidget(9, 0, textLabel); 
	gridLayout->setWidget(9, 1, _textEdit);

	connect(this, Signal_AssetChanged, &ButtonPanel::slotAssetChanged);

	connect(_formComboBox, Signal_ValueChanged, &ButtonPanel::slotFormChanged);
	connect(_alignButton, Signal_Checked, &ButtonPanel::slotAlignButtonChecked);
	connect(_alignWidget, Signal_AlignChanged, &ButtonPanel::slotAlignChoosed);
	connect(_alignWidget, Signal_Focused, &ButtonPanel::slotAlignWidgetFocused);
	connect(_textEdit, Signal_EditFinished, &ButtonPanel::slotTextEdited);
	connect(_imageButton, Signal_Clicked, &ButtonPanel::slotChooseImageFile);
	connect(_iconWidthSpinBox, Signal_EditFinished, &ButtonPanel::slotIconSizeEdited);
	connect(_iconHeightSpinBox, Signal_EditFinished, &ButtonPanel::slotIconSizeEdited);
}

void ButtonPanel::slotCheckableChanged(BObject* object, const BValue& value)
{
	bool checked = value;
	_button->setCheckable(checked);
}
void ButtonPanel::slotAssetChanged()
{
	_button = this->asset();

	if (_button)
	{
		_alignWidget->setAlign(_button->align());

		_formComboBox->setValue(_button->form());
		_alignButton->setText(_alignWidget->alignText());
		_textEdit->setText(_button->text());
		if (BImage* image = _button->image())
		{
			_imageButton->setImage(image);
			_imageButton->setText(image->fileName());
		}
		else
		{
			_imageButton->setImage(0);
			_imageButton->setText(BString());
		}
		_iconWidthSpinBox->setValue(_button->iconSize().width());
		_iconHeightSpinBox->setValue(_button->iconSize().height());
	}
}

void ButtonPanel::slotFormChanged(BObject* object, const BValue& value)
{
	Form form = value;
	_button->setForm(form);
}
void ButtonPanel::slotAlignButtonChecked()
{
	if (_alignButton->checked())
	{
		BPoint point = this->mapFrom(_alignButton, BPoint(0, _alignButton->height()));
		_alignWidget->setPos(point);
		_alignWidget->popup();
	}
	else
	{
		_alignWidget->hide();
	}
}
void ButtonPanel::slotAlignChoosed(BObject* object, const BValue& value)
{
	Align align = value;
	_button->setAlign(align);
	_alignButton->setText(_alignWidget->alignText());
	_alignButton->setChecked(false);
}
void ButtonPanel::slotAlignWidgetFocused(BObject* object, const BValue& value)
{
	if (value == false)
	{
		_alignButton->setChecked(false);
	}
}
void ButtonPanel::slotSpacingChanged(BObject* object, const BValue& value)
{
	int spacing = value;
	_button->setSpacing(spacing);
}
void ButtonPanel::slotColorButtonChecked(BObject* object, const BValue& value)
{
	const BColor& color = BColorDialog::ChooseColor("Choose Button Color", _button->color());
	_button->setColor(color);
	_colorButton->setColor(color);
}
void ButtonPanel::slotGraphChoosed(BObject* object, const BValue& value)
{
	Graph graph = value;
	_button->setGraph(graph);
}
void ButtonPanel::slotChooseIconFile()
{
	const BString& fileName = BFileDialog::OpenFile("Choose Image File", "data", "png, jpg, tiff, bmp");
	BIcon* icon = new BIcon(fileName);
	_button->setIcon(icon);
	_iconButton->setIcon(icon);
	_iconButton->setText(fileName);
}
void ButtonPanel::slotChooseImageFile()
{
	const BString& fileName = BFileDialog::OpenFile("Choose Image File", "data", "png, jpg, tiff, bmp");
	BImage* image = new BImage(fileName);
	_button->setImage(image);
	_imageButton->setImage(image);
	_imageButton->setText(fileName);
}
void ButtonPanel::slotIconSizeEdited(BObject* object, const BValue& value)
{
	int imageWidth = _iconWidthSpinBox->value();
	int imageHeight = _iconHeightSpinBox->value();
	_button->setIconSize(BSize(imageWidth, imageHeight));
}
void ButtonPanel::slotTextEdited(BObject* object, const BValue& value)
{
	const BString& text = value;
	_button->setText(text);
}

